package org.shagin.jfin.date.cond;

import static org.shagin.jfin.date.DateUtils.CLOSE_DATE;
import static org.shagin.jfin.date.DateUtils.OPEN_DATE;
import static org.shagin.jfin.date.DateUtils.isEqual;

import java.io.Serializable;
import java.text.SimpleDateFormat;
import java.util.Date;

import org.shagin.jfin.date.DateUtils;

/**
 * The Class DateRange.
 */
@SuppressWarnings("serial")
public class DateRange implements Cloneable, Serializable {

    private Date start = CLOSE_DATE;
    private Date end = OPEN_DATE;

    /**
     * Instantiates a new date range.
     */
    public DateRange() {
    }

    /**
     * Instantiates a new date range.
     * 
     * @param start the start
     * @param end the end
     */
    public DateRange(Date start, Date end) {
        set(start, end);
    }

    /**
     * Contain.
     * 
     * @param date the date
     * @return true, if successful
     */
    public boolean contain(Date date) {
        return (date.after(start) && date.before(end)) || isStart(date)
                || isEnd(date);
    }

    /**
     * Checks if is end.
     * 
     * @param date the date
     * @return true, if is end
     */
    public boolean isEnd(Date date) {
        return isEqual(date, end);
    }

    /**
     * Checks if is start.
     * 
     * @param date the date
     * @return true, if is start
     */
    public boolean isStart(Date date) {
        return isEqual(date, start);
    }

    /**
     * Gets the start.
     * 
     * @return the start
     */
    public Date getStart() {
        return start;
    }

    /**
     * Sets the start.
     * 
     * @param start the new start
     */
    public void setStart(Date start) {
        this.start = start;
    }

    /**
     * Sets the closed.
     */
    public void setClosed() {
        this.start = DateUtils.CLOSE_DATE;
    }

    /**
     * Sets the opened.
     */
    public void setOpened() {
        this.end = DateUtils.OPEN_DATE;
    }
    
    /**
     * Gets the end.
     * 
     * @return the end
     */
    public Date getEnd() {
        return end;
    }

    /**
     * Sets the end.
     * 
     * @param end the new end
     */
    public void setEnd(Date end) {
        this.end = end;
    }

    /**
     * Sets the.
     * 
     * @param start the start
     * @param end the end
     */
    public void set(Date start, Date end) {
        this.start = start;
        this.end = end;
    }

    /**
     * Sets the.
     * 
     * @param another the another
     */
    public void assign(DateRange another) {
        this.start = new Date(another.start.getTime());
        this.end = new Date(another.end.getTime());
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public String toString() {
        final SimpleDateFormat fmt = DateUtils.getSimpleDateFormat();
        return "[ " + fmt.format(start) + " , " + fmt.format(end) + " ]";
    }

    /**
     * Checks if is open date.
     * 
     * @return true, if is open date
     */
    public boolean isOpenDate() {
        return isEqual(OPEN_DATE, end);
    }

    /**
     * Checks if is close date.
     * 
     * @return true, if is close date
     */
    public boolean isCloseDate() {
        return isEqual(CLOSE_DATE, start);
    }
}
